home *** CD-ROM | disk | FTP | other *** search
-
- NKCC - NORMALIZED KEY CODE CONVERTER
- =============================================================================
- Release 2.91
-
- Written by Harald Siegmund Copyright (c) 1989-1994
-
- NKCC is Public Domain and may be used by anyone. Don't change or delete any
- files of the NKCC folder. Please put a small note in your application's
- info box if it contains NKCC (for example "Keyboard handler by Harald
- Siegmund"). Thanx!
- -----------------------------------------------------------------------------
- Documentation and program history:
-
- 1989:
- May 14: introducing NKCC (release 1.00)
- Jun/Jul: improvements, changes, debugging
-
- 1990:
- Jan 13: further improvements
- May 27-28: creation of file
- (complete new documentation for NKCC 2.x)
- Jun 16-27: multi event assembler entry added by Gerd Knops
- Jun 30: release 1.10: return shift state flags (returned by
- nkc_multi()) compatible to NKF_... flags
- Jul 09: release 1.20: new function: nkc_kstate()
- Aug 03: release 1.30: new function: nkc_cmp()
- Aug 18: bug fixed in nkc_kstate()
- Sep 15-16: release 1.40: mouse button event handler; nkc_timer()
- Oct 03: renaming NKCC II release 1.40 to NKCC release 2.40
- function overview
- Oct 30: removing chapter 6 (notes for users of NKCC 1.xx)
- Nov 13: release 2.41: NK_LEFT and NK_RIGHT exchanged
- Dec 11: release 2.50: MU_XTIMER
-
- 1991:
- Jan 11: release 2.51: better handling of MU_XTIMER
- Apr 14: release 2.60: nkc_conv() renamed to nkc_tconv();
- new function nkc_gconv()
- rearranging and partly rewriting documentation
- May 10: release 2.61 (debugging)
- May 29: release 2.62: nkc_toupper, nkc_tolower
- Jun 08: doing some small corrections of the documentation
- Aug 06: release 2.63: quote (") is now used as synonym for
- umlaut (¨) in deadkey handling
- Aug 07: more deadkeys...
- Aug 22: release 2.70:
- deadkeys can now be enabled/disabled separately
- additional note in 3.b)
- nkc_init() now returns version #
- Sep 07: release 2.71:
- nkc_cmp() improved
- NKF_RESVD is now used:
- in key codes for internal purposes!
- in reference key code (nkc_cmp()) as flag
- Nov 05: release 2.72:
- adjustments to ASCII input feature of TOS 3.06
- Nov 16: release 2.80:
- small bug fixed in nkc_cmp()
- control key emulation (NKS_CTRL) (see chapter 1)
- Dec 29: minor changes in source documentation;
- a few new (less important) symbols were added
-
- 1992:
- Jan 03/06: introducing release 2.81:
- - nkc_init's first parameter is now an unsigned long
- - the symbolic identifiers BE_ON/OFF/TOS are redefined,
- but still have the same meaning
- - new symbols: NKI_...
- - chapters 4, 7 and 9 were adjusted respectively
- completed due to the changes in nkc_init()
- - chapters 8 and 9 got additional notes about nkc_timer()
- Feb 14: correcting documentation of nkc_exit() in chapter 4
- Feb 28: NKCOWNPB switch
-
- 1993:
- Dec 11: release 2.90:
- - NKCC_GPB.O and SDOCSYNT.S are no longer part of the package
- - Selecting the version of NKCC for assembling (GEM or TOS) is
- done by a different symbol now: NKCGEM
- - NKCC uses its own AES/VDI parameter arrays now, execpt
- for the global array, which is passed as additional
- parameter to function nkc_init()
- - nkc_toupper and nkc_tolower are functions now rather than
- arrays
- - cosmetic changes in the documentation
- - new developer address
- Dec 12: introducing new functions nkc_n2tos() and nkc_n2gem()
- (which convert key codes in normalized format back to the
- system's format; see NKCC.TXT for details)
-
- 1994:
- Feb 01: adding MausNet address to documentation
- May 19: release 2.91:
- - nkc_exit won't touch the system variable contern any longer
- because it may have been changed by a parallel running
- process
- - two new deadkeys were introduced:
- / + 2 = ½
- / + 4 = ¼
- - the synatx of MadMac's directives has been added to the NKCC
- source file (and NKCC.TXT)
-
- -----------------------------------------------------------------------------
- Developer contact:
-
- as adequate systems
- Gesellschaft für angemessene Systemlösungen mbH
- c/o Harald Siegmund
- Am Steinern Kreuz 19
- D-64297 Darmstadt
- Germany
-
- e-mail address: Harald_Siegmund@kl.maus.de
-
- =============================================================================
- Table of contents
-
- 1. What is NKCC?
- 2. Files on the disk
- 3. The normalized key code format
- 4. NKCC usage
- 5. NKCC in TOS applications
- 6. NKCC in GEM applications
- 7. The button event handler
- 8. Other fine extra features
- 9. Symbol overview
-
-
-
-
- 1. What is NKCC?
- =============================================================================
- Did you ever try to program a complex keyboard handling? Then you sure know
- some of the problems coming out of TOS along with the key codes ...
-
- a) pressing Alternate + any letter will only return the scan code, which is
- TOS version-dependend (language)
-
- b) some keys get different scan codes when being pressed together with
- Alternate! For example, hitting the '1' key will return a scan code
- of 2 (on the German TOS) and an ASCII code of $31 (that's ok). The key
- combination Alternate + '1' results in a scan code of $78 and an ASCII
- code of 0!
-
- c) the cursor keypad (arrows, Insert, ClrHome, Help and Undo) is a whole
- chaos! Some of the keys change their scan code when being pressed
- together with Control. The returned ASCII code is total rubbish and
- follows no rule.
-
- d) some different key combinations return the same key codes. In most cases,
- Alternate+any key and Alternate+Shift+any key cannot be distinguished.
-
- The solution: the Normalized Key Code Converter
-
- NKCC solves all of this problems. It converts key codes received from GEMDOS
- or GEM (multi event) to an own, sophisticated format, which allows to detect
- all possible key combinations. In addition, NKCC offers some special
- features:
-
- a) Deadkey handling
-
- People in countries which know characters with accents often have the
- problem that they can't reach every character directly from the keyboard.
- Or imagine a guy who wants to type a French text on a UK TOS - without
- having characters like Ç or ë! This can be done if NKCC was built in his
- favourite word processor. It transforms combinations of key strokes to
- one character. The first one is called the deadkey: when you type it,
- nothing happens - yet. After the second key stroke, NKCC decides what to
- do. If matching with the first one, it merges both to one key code (for
- example: ~ plus A will result in Ã). If not matching, the program
- will get both keys (e.g. ~ plus X will directly be passed through the
- deadkey manager). Deadkeys known by NKCC are
-
- ^ + aeiou = âêîôû
- ~ + nNaoAo = ñÑãõÃÕ
- ' + eEaiou = éÉáíóú
- ` + aeiouA = àèìòùÀ
- ¨ + aeiouyAOU = äëïöüÿÄÖÜ
- " + aeiouyAOU = äëïöüÿÄÖÜ
- ° + aA = åÅ
- , + cC = çÇ
- / + oO24 = øØ½¼
-
- The quote character as synonym for umlaut is e.g. needed on the Dutch
- keyboard, where neither umlaut characters nor the umlaut itself are
- available.
-
- b) Direct input of ASCII codes
-
- NKCC allows the ASCII code of characters to be input directly. Just press
- the Alternate key and hold it. Then type in the ASCII code on the numeric
- keyboard (as decimal number). The input is finished when either the
- Alternate key is relased or three digits are typed in. Values beyond 255
- are truncated to 8 bit (e.g. 260 ($104) becomes 4).
-
- c) Control key emulation
-
- Usually, NKCC returns key combinations like "Control A" as ASCII code $41
- (for "A") and with a set Control key flag. If the control key emulation
- is enabled, "Control A" will return an ASCII code of $01. The Control key
- flag will be cleared in this case.
-
- The Control key emulation converts ...
-
- Control + @ to $00
- Control + A...Z to $01...$1A
- Control + [ to $1B
- Control + \ to $1C
- Control + ] to $1D
- Control + ^ to $1E
- Control + _ to $1F
-
- Important note:
-
- On several keyboards, some of the key combinations in the list above
- cannot be recognized and thus not converted. For example, on the German
- keyboard, the characters "@", "[", "\" and "]" can't be typed in together
- with the Control key. Their ASCII codes don't appear in any of the TOS
- key code tables, because they can only be reached when holding the
- Alternate key. Unfortunately, TOS returns the wrong ASCII code when
- Control is also held down, making it impossible to find out the original
- ASCII value.
-
-
- Every deadkey and special feature can be enabled/disabled separately.
-
- The best way to see how NKCC works is to start the test utility (TEST.TOS)
- and hack on the keyboard.
-
-
-
- 2. Files on the disk
- =============================================================================
- The NKCC folder/disk/archive/whatever should contain the following files:
-
- NKCC.S source of NKCC
- NKCC.SH assembler header file with NKCC definitions
- NKCC.H C header file with NKCC definitions
- NKCC.O NKCC as object file (DRI format)
- NKCC_TOS.O NKCC as object file without GEM part (DRI format)
- NKCC.TXT excerpt of NKCC.S with all global definitions
- NKCC.DOC this documentation!
- TEST.C source of small test utility
- TEST.TOS test utility as executable program
- WHATSNEW.TXT information about all new features since the last release
-
-
-
-
- 3. The normalized key code format
- =============================================================================
- NKCC returns key codes as 16 bit integer. The low byte contains the ASCII
- part of the key, the high byte is the location for some flags. Here's the
- complete format:
-
- Bit # Symbolic name Contents
- ------------------------------------------------------------
- 0... 7 ASCII code/key code
- 8 NKF_LSH left Shift key flag
- 9 NKF_RSH right Shift key flag
- 10 NKF_CTRL Control key flag
- 11 NKF_ALT Alternate key flag
- 12 NKF_CAPS current state of CapsLock key
- 13 NKF_NUM numeric keypad flag
- 14 NKF_RESVD reserved(!) for internal purposes
- 15 NKF_FUNC function flag
-
- Bits 8...11 speak for themself. Bit 12 reflects the current state of the
- CapsLock key. Bit 13, if set, indicates that the key is located on the
- numeric keypad. Bit 14 is reserved for internal use and must be ignored.
- However, it has a special meaning as parameter for the function nkc_cmp(),
- described in the next chapter. Finally, the MSB of the key code (bit 15)
- specifies the key type: if set, the key code stands for any function to
- perform. If not set, it contains any printable character. The bit is set
- when
-
- a) any of the following "function keys" is pressed:
-
- Esc, Tab, Backspace, Delete, Return,
- Help, Undo, Insert, ClrHome, cursor up, cursor down, cursor left,
- cursor right,
- Enter,
- F1, F2, F3, F4, F5, F6, F7, F8, F9, F10
-
- The ASCII code for such keys is less than 32 and defined as NK_... in
- the header files (e.g. NK_ESC for Escape).
-
- b) any key is pressed together with Alternate and/or Control
-
- In this case, NKCC always returns the CapsLock variant of a key (e.g.
- the ASCII part of the key combination Control + A is 'A' rather than
- 'a').
-
-
- The function flag was intentionally placed in bit 15 to ease its handling:
-
- if (keycode < 0)
- perform function
- else
- use printable character
-
- The ASCII code of a printable character spans over the whole number range
- of an unsigned byte: from 0 up to 255.
-
-
- Please note that some key combinations cannot be caught by NKCC:
-
- a) keys which are hold back by TOS: any key of the cursor pad plus Alternate
- (except Alternate + Undo); they are used for mouse controlling and to
- start a screen hardcopy.
-
- b) characters which can only be typed in when pressing Alternate, such as
- @\[{]} on the German keyboard. They are treated correctly by NKCC, but
- they never appear with a set Alternate flag.
-
-
- Characters created by the deadkey handler or the direct ASCII input are
- returned as if present on the keyboard. None of the flags, except CapsLock,
- can be set. Key codes created by the Control key emulation never appear with
- a set Control key flag.
-
-
-
-
- 4. NKCC usage
- =============================================================================
- Working with NKCC is rather simple. Only a few functions have to be called.
-
- Before receiving the first key code, NKCC has to be initialized by an
- nkc_init() call. nkc_init() gets three parameters: The first is a 32 bit
- integer with some flags, defined as NKI_... in the header file NKCC.H
- (respectively NKIb_.../NKIf_... in NKCC.SH). The following flags exist:
-
- NKI_BUTHND are both used to control the built-in handler for mouse
- NKI_BHTOS button events, described in the chapter "The button event
- handler"
-
- NKI_NO200HZ if set, NKCC won't install the timer interrupt used for
- the function nkc_timer(). Note: if the button event
- handler is being activated, this flag is ignored because
- the timer is needed then for NKCC-internal purposes.
-
- nkc_init()'s second parameter is the handle of a virtual VDI workstation,
- also needed for the button event handler. It may be zero if the handler is
- not installed.
-
- At last the third parameter is a pointer to the applications GLOBAL array
- (one of the AES parameter arrays). The pointer isn't used by NKCC_TOS.O.
- When using NKCC in applications developed with Turbo C respectively Pure C
- this parameter is _GemParBlk.global (defined in AES.H).
-
- The function returns a 16 bit integer with NKCC's version number as
- 4 digit BCD (main # in high byte, sub # in low byte).
-
- The most simple call of nkc_init() would be:
-
- nkc_init(0,0,NULL);
-
-
- Accordingly, NKCC has to be turned off before your program is quit. This is
- done by an nkc_exit() call. The function has no input parameters, but
- returns a status code: if NKCC has linked itself into the system vectors,
- and somebody has corrupted the XBRA vector list, it will be unable to
- deinstall and returns an according error code. This is fatal! Your program
- must not terminate in this case! Show a warning message and tell the user
- to reboot.
-
-
- NKCC offers several methods to receive key codes. Their main difference is
- the kind of program NKCC is linked to: TOS or GEM application/accessory.
- Consult the according chapters for details.
-
-
- The special handlers for direct ASCII input, deadkey handling etc. are
- controled via the function nkc_set(). The function gets a long integer with
- 32 flags as parameter. A set flag enables the feature, a cleared flag
- disables it. Their symbolic names are:
-
- NKS_ALTNUM for direct ASCII input
- NKS_CTRL for control key emulation
- NKS_D_... for deadkey management
-
-
- When comparing two normalized key codes, no direct check should be made
- (like: if (key1 == key2) ...)! Use the function nkc_cmp() instead. It uses
- some specific rules which improve the flexibility of key code comparism.
- The function gets two key key codes as parameters, one called "reference
- key code" and the other "test key code". Some bits of the reference key code
- (the first parameter) are treated a special way:
-
- NKF_IGNUM (same as NKF_RESVD)
- if set, the numeric keypad flag doesn't matter
-
- NKF_CAPS (CapsLock state)
- if set, the case of the ASCII code doesn't matter
-
- NKF_SHIFT (both Shift keys; identical to NKF_LSH | NKF_RSH)
- if BOTH shift flags are set in the reference key code, the combination of
- shift key flags in the test key code doesn't matter: only one shift flag
- has to be set, no matter which one.
-
-
-
-
- 5. NKCC in TOS applications
- =============================================================================
- When being used in a TOS type program (without windows, AES dialogs and
- mouse), the TOS-version of NKCC should be used (file NKCC_TOS.O). Some
- functions for multi event and mouse handling are missing in that file,
- making it some KBytes smaller.
-
- The functions, which have to be called, are:
-
- nkc_conin()
- works similar to the GEMDOS functions Cconin()/Crawcin() or the BIOS
- function Bconin(2). It waits until a key is pressed and returns its code
- in normalized format, as 16 bit integer. The function bases on GEMDOS'
- Crawcin(). If you like to use Cconin() or Bconin(), just change the
- system call in the NKCC source.
-
- nkc_cstat()
- replaces Cconis() respectively Bconstat(). It checks, if there is any key
- code in the OS internal key buffer and returns an according status:
- 0=no key, -1=at least one key in buffer
-
-
-
-
- 6. NKCC in GEM applications
- =============================================================================
- In GEM applications or accessories, NKCC replaces the whole multi event
- handler with its function nkc_multi(), which gets the same parameters as
- usual C multi event bindings. The differences are:
-
- a) key codes are returned in normalized format
-
- b) the key state is returned NKCC compatible, which means: key state flags
- are placed in bits 8...11 rather than bits 0...3 and can be testet using
- the NKF_... symbols
-
-
- There's no NKCC function which replaces evnt_keybd(). Please use nkc_multi()
- instead - or write your own binding!
-
-
-
- Special extension for assembler programmers - by Gerd Knops
- ------------------------------------------------------------
-
- When using the event_multi-routine, you probably have code like
- this in your source-code:
-
- ... setting up the aes-arrays, then
- bsr aes
-
- with
-
- aes: move.l #aespb,d1
- move #$c8,d0
- trap #2
- rts
-
- Simply replace 'bsr aes' with 'bsr nkc_amulti'. Note, that you
- have to use the AES-arrays from NKCC for this purpose.
- See chapter 9 for a symbol overview.
-
-
-
- 7. The button event handler
- =============================================================================
- Some years ago Atari released the long awaited TOS version 1.04. It had some
- very nice new features and improvements. TOS 1.04 (or a higher version) is a
- must for every ST user. Unfortunately, the guys in Sunnyvale messed up the
- multi event handler in the AES, making it impossible to receive mouse button
- events and timer events with short cycle times in one evnt_multi() call,
- without having big problems with the double click: the multi event returns
- immediately when a timer event occurs. If it was just processing a mouse
- click (waiting for a possible second click), the resulting event mask is
- MU_TIMER *and* MU_BUTTON! No chance to get through a double click.
-
- I spent hours to find a way how I could bypass this problem. Finally, I
- decided to write an own mouse button event handler, and put it into NKCC.
-
- The NKCC button event handler is activated at initialization time. Two flags
- in the longword passed to nkc_init() control whether the handler should be
- installed or not:
-
- NKI_BUTHND install it
-
- NKI_BUTHND|NKI_BHTOS install it, if TOS version has mouse click bug (TOS
- version >= 1.04 and < 3.06)
-
- If the NKI_BUTHND flag is not set, the handler will not be installed (the
- state of the NKI_BHTOS flag is ignored in this case).
-
- The second parameter of nkc_init() is the handle of a virtual VDI
- workstation, which had to be opened by NKCC's caller (NKCC uses a VDI
- vex_butv() call). The workstation may not be closed until nkc_exit() was
- called. If the mouse button event handler has not been installed, the
- handle is ignored.
-
- Another fine feature of the button event handler is an additional flag in
- the event mask: MU_XTIMER. If this flag is set (together with MU_TIMER),
- timer events will only return if no redraw-critical user action is taken
- (like moving windows or sliding through the menu bar). This prevents redraw
- problems, e.g. when the timer event is used to update a mouse coordinate
- display.
-
- Note: the NKCC button event handler supports the (undocumented) negation
- flag, which is passed in bit 8 of the parameter <bclicks> (maximum # of
- mouse clicks to wait for). You don't know this flag? I found an article
- about it in the c't magazine (I think it was issue 3/90, or maybe 4/90??) -
- and I damned Atari for their bad documentation. This flag opens the way to
- check BOTH mouse buttons at the same time without any problems. When set,
- the return condition is inverted. Let's have a look at an example:
-
- mask = evnt_multi(MU_BUTTON,2,3,3,...
-
- This doesn't work the way we want: the return condition is "button #0
- pressed AND button #1 pressed". But look at this:
-
- mask = evnt_multi(MU_BUTTON,0x102,3,0,...
-
- Now the condition is "NOT (button #0 released AND button #1 released)". Or
- in other words: "button #0 pressed OR button #1 pressed". Nice, isn't it?!
-
-
- Final note: the mouse click bug is fixed since TOS version 3.06.
- Thanks to Atari Corp.!
-
-
-
-
- 8. Other fine extra features
- =============================================================================
- NKCC includes some functions primary built in for its own purposes. However,
- some of this functions could also be useful for the programmers using NKCC,
- so they are exported and documented. Here's a list of them:
-
- nkc_timer()
- returns the current value of the 200 Hz system clock as unsigned longword.
- The function is very fast, because it just has to copy the value from an
- internal static variable to the return register.
-
- Note: if NKCC's timer interrupt is not installed, the function will
- always return 0. See chapter 4 for details.
-
- nkc_kstate()
- returns the current state of the Shift, Control, Alternate and CapsLock
- keys in NKCC compatible format. This function is very fast, too!
-
- nkc_tconv()
- is the heart of NKCC: the raw key code converter, which transforms a TOS
- key code to the normalized format. However, it does not perform deadkey
- handling, ASCII input or Control key emulation.
-
- nkc_gconv()
- is a variant of nkc_tconv(), which gets the key code in GEM format (16
- bit integer instead of 32 bit, and NO KEY STATE FLAGS!). nkc_gconv() is
- surely not perfect - but that's no NKCC's fault! The key state flags are
- very very important for proper conversion, and without them, several
- key combinations cannot be distinguished (as meantioned in the first
- chapter of this documentation). Whenever possible, use nkc_tconv()!
- nkc_gconv() is more an emergency exit, which should only be used when the
- key state flags are lost.
-
- nkc_n2tos()
- converts normalized key codes back to TOS format key codes.
-
- nkc_n2gem()
- converts normalized key codes back to GEM format key codes.
-
- nkc_vlink()
- This function links a standard XBRA routine to a vector list. The vector
- can be chosen either as absolute address (e.g. $502 for the hardcopy
- vector) or as number (e.g. $02 for the bus error handler vector).
-
- nkc_vunlink()
- The counterpart of nkc_vlink(). A function is removed from an XBRA vector
- list.
-
- nkc_toupper()
- A character is converted to upper case. In contrast to most C compiler
- library functions (ctypes.h) this functions treats foreign language
- characters (e.g. 'ä', 'é') correctly!
-
- nkc_tolower()
- The counterpart of the previous function: a character is converted to
- lower case.
-
-
- For a detailed documentation of the functions consult NKCC.TXT.
-
-
-
-
- 9. Symbol overview
- =============================================================================
- Here's an overview of all symbols exported by NKCC. Functions are marked
- with parentheses behind the symbol name:
-
- nkc_init() initialize and configure NKCC, optional installation of an
- own mouse button event handler
- nkc_exit() exit NKCC (unlink own functions from the system etc.)
- nkc_set() enable/disable the special key handler functions
- (deadkeys, direct ASCII input, Control key emulation)
- nkc_conin() raw console character input in NKCC format (based on
- GEMDOS' Crawcin())
- nkc_cstat() sample console input status (based on GEMDOS' Cconis())
- * nkc_multi() AES multi event binding, which returns key codes and shift
- key flags in normalized format
- * nkc_amulti() AES multi event binding for assembler programs
- nkc_tconv() raw key code converter (TOS -> normalized format)
- nkc_gconv() additional key code converter (GEM -> normalized format)
- nkc_n2tos() additional key code converter (normalized format -> TOS)
- nkc_n2gem() additional key code converter (normalized format -> GEM)
- nkc_kstate() sample state of Shift, Control, Alternate and CapsLock
- keys in normalized format; very fast!
- nkc_timer() return current timer value of 200 Hz system clock; very
- fast! Note: if timer is disabled, the function always
- returns 0 (see chapter 4)
- nkc_cmp() compare two key codes due to standard comparism rules
- nkc_vlink() link function to XBRA vector list
- nkc_vunlink() unlink function from XBRA vector list
- nkc_toupper() lower case -> upper case conversion
- nkc_tolower() upper case -> lower case conversion
-
- * nkc_contrl AES/VDI control array
- * nkc_intin AES/VDI integer input array
- * nkc_intout AES/VDI integer output array
- * nkc_adrin AES address input array
- * nkc_adrout AES address output array
- (unfortunately the correct names - addrin and addrout -
- would create a doubly defined symbol because the
- DRI object file format supports only 8 characters per
- symbol - gosh!)
- * nkc_ptsin VDI pointers input array
- * nkc_ptsout VDI pointers output array
- (all arrays used for nkc_amulti())
-
-
- * not available in NKCC_TOS.O which is for TOS applications and excludes
- the GEM part of NKCC (assembled with the NKCGEM symbol set to 0; see
- header of NKCC.TXT)
-
- =============================================================================
- End Of File
-